#include "reply.h"

#include <algorithm>

#include "bufferutil.h"

namespace b2gdns {

	void Reply::encode_header(char*& buffer)
	{
		write16bits(buffer, header_.id);
		unsigned short bytes3and4 = (header_.qr << 15);
		bytes3and4 += (header_.opcode << 11);
		bytes3and4 += (header_.aa << 10);
		bytes3and4 += (header_.tc << 9);
		bytes3and4 += (header_.rd << 8);
		bytes3and4 += (header_.ra << 7);
		bytes3and4 += (header_.z << 4);
		bytes3and4 += header_.rcode;
		write16bits(buffer, bytes3and4);
		write16bits(buffer, header_.qdCount);
		write16bits(buffer, header_.anCount);
		write16bits(buffer, header_.nsCount);
		write16bits(buffer, header_.arCount);
	}

	void Reply::encode_question(char*& buffer)
	{
		std::for_each(question_.begin(), question_.end(), [&buffer](std::string const& q)
		{
			std::size_t start = 0, end; // indexes
			while ((end = q.find('.', start)) != std::string::npos)
			{
				*buffer++ = static_cast<char>(end - start); // label length octet
				for (std::size_t i = start; i < end; i++)
					*buffer++ = q[i]; // label octets
				start = end + 1; // Skip '.'
			}
			*buffer++ = static_cast<char>(q.size() - start); // last label length octet
			for (std::size_t i = start; i < q.size(); i++)
				*buffer++ = q[i]; // last label octets
			*buffer++ = 0;
		});
	}

} // namespace b2gdns
